
package cn.xabad.commons.io.input;

import java.io.Reader;
import java.io.Serializable;


public class CharSequenceReader extends Reader implements Serializable {

    private final CharSequence charSequence;
    private int idx;
    private int mark;

    
    public CharSequenceReader(CharSequence charSequence) {
        this.charSequence = charSequence != null ? charSequence : "";
    }

    
    @Override
    public void close() {
        idx = 0;
        mark = 0;
    }

    
    @Override
    public void mark(int readAheadLimit) {
        mark = idx;
    }

    
    @Override
    public boolean markSupported() {
        return true;
    }

    
    @Override
    public int read() {
        if (idx >= charSequence.length()) {
            return -1;
        } else {
            return charSequence.charAt(idx++);
        }
    }

    
    @Override
    public int read(char[] array, int offset, int length) {
        if (idx >= charSequence.length()) {
            return -1;
        }
        if (array == null) {
            throw new NullPointerException("Character array is missing");
        }
        if (length < 0 || offset < 0 || offset + length > array.length) {
            throw new IndexOutOfBoundsException("Array Size=" + array.length +
                    ", offset=" + offset + ", length=" + length);
        }
        int count = 0;
        for (int i = 0; i < length; i++) {
            int c = read();
            if (c == -1) {
                return count;
            }
            array[offset + i] = (char)c;
            count++;
        }
        return count;
    }

    
    @Override
    public void reset() {
        idx = mark;
    }

    
    @Override
    public long skip(long n) {
        if (n < 0) {
            throw new IllegalArgumentException(
                    "Number of characters to skip is less than zero: " + n);
        }
        if (idx >= charSequence.length()) {
            return -1;
        }
        int dest = (int) Math.min(charSequence.length(), idx + n);
        int count = dest - idx;
        idx = dest;
        return count;
    }

    
    @Override
    public String toString() {
        return charSequence.toString();
    }
}
